<!DOCTYPE html
  PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<!-- saved from url=(0014)about:internet -->
<html xmlns:MSHelp="http://www.microsoft.com/MSHelp/" lang="en-us" xml:lang="en-us"><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8">

<meta name="DC.Type" content="topic">
<meta name="DC.Title" content="More on HashCompare">
<meta name="DC.subject" content="More on HashCompare">
<meta name="keywords" content="More on HashCompare">
<meta name="DC.Relation" scheme="URI" content="../tbb_userguide/concurrent_hash_map.htm">
<meta name="DC.Format" content="XHTML">
<meta name="DC.Identifier" content="tutorial_More_on_HashCompare">
<link rel="stylesheet" type="text/css" href="../intel_css_styles.css">
<title>More on HashCompare</title>
<xml>
<MSHelp:Attr Name="DocSet" Value="Intel"></MSHelp:Attr>
<MSHelp:Attr Name="Locale" Value="kbEnglish"></MSHelp:Attr>
<MSHelp:Attr Name="TopicType" Value="kbReference"></MSHelp:Attr>
</xml>
</head>
<body id="tutorial_More_on_HashCompare">
 <!-- ==============(Start:NavScript)================= -->
 <script src="..\NavScript.js" language="JavaScript1.2" type="text/javascript"></script>
 <script language="JavaScript1.2" type="text/javascript">WriteNavLink(1);</script>
 <!-- ==============(End:NavScript)================= -->
<a name="tutorial_More_on_HashCompare"><!-- --></a>


<h1 class="topictitle1">More on HashCompare</h1>

<div><p>There are several ways to make the <samp class="codeph"><var>HashCompare</var></samp> argument for <samp class="codeph">concurrent_hash_map</samp> work for your own types.</p>

<ul type="disc"><li><p>Specify the <samp class="codeph"><var>HashCompare</var></samp> argument explicitly</p>
</li>
<li><p>Let the <samp class="codeph"><var>HashCompare</var></samp> default to <samp class="codeph">tbb_hash_compare&lt;<var>Key</var>&gt;</samp> and do one of the following:</p>

<ul type="disc"><li><p>Define a specialization of template <samp class="codeph">tbb_hash_compare&lt;<var>Key</var>&gt;</samp>.</p>
</li>
<li><p>Define an overload of function <samp class="codeph">tbb_hasher(<var>Key</var>)</samp>.</p>
</li>
<li><p>Rely on the definitions of <samp class="codeph">tbb_hasher(<var>Key</var>)</samp> provided by the library.</p>
</li>
</ul>
</li>
</ul>
<p>Function <samp class="codeph">tbb_hasher</samp> is predefined for the following types: </p>

<ul type="disc"><li><p>Types convertible to <samp class="codeph">size_t</samp>, such as integral types. </p>
</li>
<li><p>Pointer types.</p>
</li>
<li><p>Instances of <samp class="codeph">std::basic_string</samp>.</p>
</li>
<li><p><samp class="codeph">std::pair&lt;<var>Key1</var>,<var>Key2</var>&gt;</samp>, where <samp class="codeph">tbb_hasher(<var>Key</var>)</samp> and <samp class="codeph">tbb_hasher(<var>Key2</var>)</samp> are defined.</p>
</li>
</ul>
<p>For example, if you have keys of type <samp class="codeph">Foo</samp>, and <samp class="codeph">operator==</samp> is defined for <samp class="codeph">Foo</samp>, you just have to provide a definition of <samp class="codeph">tbb_hasher</samp> as shown below: </p>

<pre>size_t tbb_hasher(const Foo&amp; f) {
    size_t h = ...compute hash code for f...
    return h;
};</pre>
<p>In general, the definition of <samp class="codeph">tbb_hash_compare&lt;<var>Key</var>&gt;</samp> or <samp class="codeph"><var>HashCompare</var></samp> must provide two signatures:</p>

<ul type="disc"><li><p>A method <samp class="codeph">hash</samp> that maps a <samp class="codeph"><var>Key</var></samp> to a <samp class="codeph">size_t</samp></p>
</li>
<li><p>A method <samp class="codeph">equal</samp> that determines if two keys are equal</p>
</li>
</ul>
<p>The signatures go together in a single class because <em>if two keys are equal, then they must hash to the same value</em>, otherwise the hash table might not work. You could trivially meet this requirement by always hashing to <samp class="codeph">0</samp>, but that would cause tremendous inefficiency. Ideally, each key should hash to a different value, or at least the probability of two distinct keys hashing to the same value should be kept low.</p>
<p>The methods of <samp class="codeph"><em>HashCompare</em></samp> should be <samp class="codeph">static</samp> unless you need to have them behave differently for different instances. If so, then you should construct the <samp class="codeph">concurrent_hash_map</samp> using the constructor that takes a <samp class="codeph"><em>HashCompare</em></samp> as a parameter. The following example is a variation on an earlier example with instance-dependent methods. The instance performs both case-sensitive or case-insensitive hashing, and comparison, depending upon an internal flag <samp class="codeph">ignore_case</samp>.</p>

<pre>// Structure that defines hashing and comparison operations
class VariantHashCompare {
    // If true, then case of letters is ignored.
    bool ignore_case;
public:
    size_t hash(const string&amp; x) const {
        size_t h = 0;
        for(const char* s = x.c_str(); *s; s++) 
            h = (h*16777179)^*(ignore_case?tolower(*s):*s);
        return h;
    }
    // True if strings are equal
    bool equal(const string&amp; x, const string&amp; y) const {
        if( ignore_case )
            strcasecmp(x.c_str(), y.c_str())==0;
        else
            return x==y;
    }
    VariantHashCompare(bool ignore_case_) : ignore_case(ignore_case_) {}
};
&nbsp;
typedef concurrent_hash_map&lt;string,int, VariantHashCompare&gt; VariantStringTable;
&nbsp;
VariantStringTable CaseSensitiveTable(VariantHashCompare(false));
VariantStringTable CaseInsensitiveTable(VariantHashCompare(true));</pre>
<p>The directory <samp class="codeph">examples/concurrent_hash_map/count_strings</samp> contains a complete example that uses <samp class="codeph">concurrent_hash_map</samp> to enable multiple processors to cooperatively build a histogram. </p>
</div>

<div class="familylinks">
<div class="parentlink"><strong>Parent topic:</strong>&nbsp;<a href="../tbb_userguide/concurrent_hash_map.htm">concurrent_hash_map</a></div>
</div>
<div></div>

</body>
</html>
